home *** CD-ROM | disk | FTP | other *** search
/ Power Programmierung 2 / Power-Programmierung CD 2 (Tewi)(1994).iso / c / library / dos / grafik / cgazv5n3 / topdown.c < prev    next >
Encoding:
C/C++ Source or Header  |  1991-02-27  |  4.7 KB  |  181 lines

  1. /* Listing 3. TOPDOWN.C - A Top-Down Recursive-Descent Parser */
  2.  
  3. #include <stdio.h>
  4. #include <stdlib.h>
  5. #include <stdarg.h>
  6. #include "lex.h"
  7.  
  8. void expression         (void);
  9. void factor             (void);
  10. void mult_expr          (void);
  11. void mult_predicate     (void);
  12. void predicate          (void);
  13. void statement          (void);
  14. void error              (char *fmt,...);
  15.  
  16. #ifdef PTRACE
  17.      static int Rdepth = 0;
  18.      int        rdepth(void)    {return( Rdepth * 8 );}
  19. #    define     trace(name)     printf("%*s%s\n", Rdepth++ * 8, "",  name)
  20. #    define     untrace(name)   (--Rdepth)
  21. #else
  22. #    define trace(name)         /* empty */
  23. #    define untrace(name)       /* empty */
  24. #endif
  25. /*----------------------------------------------------------------------*/
  26. void statement( void )
  27. {
  28.      /* statement->WHILE LP expression RP statement     WHILE
  29.       * statement->expression SEMI                      LP SEMI ID NUMBER
  30.       */
  31.  
  32.     trace("statement");
  33.     if( match(WHILE) )
  34.     {
  35.         advance();
  36.  
  37.         if( match(LP) ) advance();
  38.         else            error("Inserting missing left parenthesis.");
  39.  
  40.         expression();
  41.  
  42.         if( match(RP) ) advance();
  43.         else            error("Inserting missing right parenthesis.");
  44.  
  45.         statement();
  46.     }
  47.     else if( match(LP) || match(SEMI) || match(ID) || match(NUMBER) )
  48.     {
  49.         expression();
  50.  
  51.         if( match(SEMI) ) advance();
  52.         else              error("Inserting missing semicolon.");
  53.     }
  54.     else
  55.         error( "while loop or expression expected\n" );
  56.  
  57.     untrace("statement");
  58. }
  59. /*----------------------------------------------------------------------*/
  60. void expression( void )
  61. {
  62.      /* expression->mult_expr predicate            LP ID NUMBER
  63.       * expression->(epsilon)                      RP SEMI
  64.       */
  65.  
  66.     trace("expression");
  67.  
  68.     if( match(LP) || match(ID) || match(NUMBER) )
  69.     {
  70.         mult_expr();
  71.         predicate();
  72.     }
  73.     else if( match(RP) || match(SEMI) )
  74.         ;                                       /* epsilon */
  75.     else
  76.         error( "expression expected\n" );
  77.  
  78.     untrace("expression");
  79. }
  80. /*----------------------------------------------------------------------*/
  81. void predicate( void )
  82. {
  83.      /* predicate->PLUS mult_expr predicate        PLUS
  84.       * predicate->MINUS mult_expr predicate       MINUS
  85.       * predicate->(epsilon)                       RP SEMI
  86.       */
  87.  
  88.     trace("predicate");
  89.  
  90.     if( match(PLUS) || match(MINUS) )
  91.     {
  92.         advance();
  93.         mult_expr();
  94.         predicate();
  95.     }
  96.     else if( match(RP) || match(SEMI) )
  97.         ;                               /* epsilon */
  98.     else
  99.         error("operator or statement-terminator expected\n");
  100.  
  101.     untrace("predicate");
  102. }
  103. /*----------------------------------------------------------------------*/
  104. void mult_expr( void )
  105. {
  106.      /* mult_expr->factor mult_predicate        LP ID NUMBER
  107.       */
  108.  
  109.     trace("mult_expr");
  110.  
  111.     if( match(LP) || match(ID) || match(NUMBER) )
  112.     {
  113.         factor();
  114.         mult_predicate();
  115.     }
  116.     else
  117.         error( "expected number identifier or open parenthesis\n" );
  118.  
  119.     untrace("mult_expr");
  120. }
  121. /*----------------------------------------------------------------------*/
  122. void mult_predicate( void )
  123. {
  124.      /* mult_predicate->STAR factor mult_predicate      STAR
  125.       * mult_predicate->SLASH factor mult_predicate     SLASH
  126.       * mult_predicate->(epsilon)         RP PLUS MINUS SEMI
  127.       */
  128.  
  129.     trace("mult_predicate");
  130.  
  131.     if( match(STAR) || match(SLASH) )
  132.     {
  133.         advance();
  134.         factor();
  135.         mult_predicate();
  136.     }
  137.     else if( match(RP) || match(PLUS) || match(MINUS) || match(SEMI) )
  138.         ;               /* epsilon */
  139.     else
  140.         error("operator expected\n");
  141.  
  142.     untrace("mult_predicate");
  143. }
  144.  
  145. /*----------------------------------------------------------------------*/
  146. void factor( void )
  147. {
  148.     /* factor->NUMBER                           NUMBER
  149.      * factor->ID                               ID
  150.      * factor->LP expression RP                 LP
  151.      */
  152.  
  153.     trace( "factor" );
  154.  
  155.     if( match(NUMBER) || match(ID) )
  156.         advance();
  157.     else if( match(LP) )
  158.     {
  159.         advance();
  160.         expression();
  161.  
  162.         if( match(RP) ) advance();
  163.         else            error("Inserting missing right parenthesis.");
  164.     }
  165.  
  166.     untrace( "factor" );
  167. }
  168. /*----------------------------------------------------------------------*/
  169. void error( char *fmt, ... )
  170. {
  171.     va_list     args;
  172.     va_start( args, fmt );
  173.     vfprintf( stderr, fmt, args );
  174.     va_end( args );
  175. }
  176. /*----------------------------------------------------------------------*/
  177. int main()
  178. {
  179.     statement();
  180.     return 0;
  181. }